package tournamentData;

import gui.mainWindow.scores.ScoresController;

import java.io.File;
import java.util.HashMap;
import java.util.LinkedList;
import java.util.Observable;

import core.Date;

public class TournamentData extends Observable {

	private static TournamentData instance = null;
	private GeneralTournamentInformation information;
	private final LinkedList < Integer > participants;
	private final HashMap < Integer, GlobalScore > scores;
	private final TargetAssignment targetAssignment;
	private int numberOfTargets;
	private int playersPerTarget;
	private File openedFile = null;

	private TournamentData() {
		this.scores = new HashMap < Integer, GlobalScore >();
		this.participants = new LinkedList < Integer >();
		this.targetAssignment = new TargetAssignment();
		this.information = new GeneralTournamentInformation("tournamentType", "tournamentName", new Date(13, 13, 13), new Date(13, 13, 13), "organizer", "tournamentLead", "referee");
		this.numberOfTargets = 1;
		this.playersPerTarget = 1;
	}

	public static TournamentData getInstance() {
		if (instance == null) {
			instance = new TournamentData();
		}
		return instance;
	}

	public void setNumberOfTargets(int numberOfTargets) {
		if (numberOfTargets > 0) {
			this.numberOfTargets = numberOfTargets;
			this.setChanged();
			this.notifyObservers();
		}
	}

	public void setPlayersPerTarget(int playersPerTarget) {
		if (playersPerTarget > 0) {
			this.playersPerTarget = playersPerTarget;
			this.setChanged();
			this.notifyObservers();
		}
	}

	public int getNumberOfTargets() {
		return this.numberOfTargets;
	}

	public int getPlayersPerTarget() {
		return this.playersPerTarget;
	}

	public void setGeneralTournamentInformation(GeneralTournamentInformation information) {
		this.information = information;
		this.setChanged();
		this.notifyObservers();
	}

	public GeneralTournamentInformation getGeneralTournamentInformation() {
		return this.information;
	}

	public void addRemovePlayer(int playerID) {
		if (this.isParticipating(playerID)) {
			this.participants.removeFirstOccurrence(playerID);
			this.getTargetAssignment().removeAssignmentForPlayer(playerID);
			this.scores.remove(playerID);
		} else {
			this.participants.add(playerID);
		}
		this.setChanged();
		this.notifyObservers();
	}

	public boolean isParticipating(int playerID) {
		return this.participants.contains(playerID);
	}

	public Integer [] getAllParticipants() {
		Integer [] toReturn = new Integer [this.participants.size()];
		for (int i = 0; i < toReturn.length; i++) {
			toReturn [i] = this.participants.get(i);
		}
		return toReturn;
	}

	public TargetAssignment getTargetAssignment() {
		return this.targetAssignment;
	}

	public GlobalScore getScore(int playerID) {
		if (!this.scores.containsKey(playerID)) {
			this.scores.put(playerID, new GlobalScore());
		}
		return this.scores.get(playerID);
	}

	public void removeScore(int playerID) {
		this.scores.remove(playerID);
	}

	public void notifyOfScoreChange(ScoresController scoresController) {
		this.setChanged();
		this.notifyObservers(scoresController);
	}

	public File getOpenedFile() {

		return this.openedFile;
	}

	public void setOpenedFile(File openedFile) {
		this.openedFile = openedFile;
	}
}
